# services/approval_service.py
from models.workflow import WorkflowTemplate, ApprovalRecord, WorkflowStep, WorkflowInstance
from models.user import User
from utils.database import db
from sqlalchemy import func


class ApprovalService:
    @classmethod
    def is_approver_userid(cls,instance_id, user_id):
        # 验证是否是合法审批人
        instance = WorkflowInstance.query.get_or_404(instance_id)
        # 获取当前步骤
        current_step = WorkflowStep.query.filter_by(
            template_id=instance.template_id,
            step_order=instance.current_step
        ).first()
        # 判断当前用户是否是当前步骤的审批人
        if user_id not in current_step.approver_ids:
            return False
        return True

    # 处理审批
    @classmethod
    def process_approval(cls, instance_id, user_id, decision, comment):
        # 根据实例id获取工作流实例
        instance = WorkflowInstance.query.get_or_404(instance_id)
        # 获取当前步骤
        current_step = instance.current_step

        # 创建审批记录
        record = ApprovalRecord(
            instance_id=instance_id,
            step_order=current_step,
            approver_id=user_id,
            decision=decision,
            comment=comment
        )
        db.session.add(record)

        # 判断当前步骤是否完成
        if cls._is_step_completed(instance):
            # 如果审批结果为拒绝，则将实例状态设置为拒绝
            if decision == 'REJECT':
                instance.status = 'REJECTED'
            else:
                # 如果是最后一个步骤，则将实例状态设置为通过
                if cls._is_final_step(instance):
                    instance.status = 'APPROVED'
                else:
                    # 否则，将当前步骤加一，并处理步骤抄送
                    instance.current_step += 1
                    WorkflowService._handle_step_cc(instance, instance.current_step)
        # 提交数据库
        db.session.commit()

    @classmethod
    def get_pending_approvals(cls, user_id, page_number=1, page_size=10):
        """
        获取指定用户的待审批流程
        逻辑变更：
        1. 直接匹配审批人列表中的用户ID
        2. 无需角色转换
        """
        subquery = db.session.query(ApprovalRecord.instance_id).filter(
            ApprovalRecord.approver_id == user_id,
            ApprovalRecord.step_order == WorkflowInstance.current_step
        ).correlate(WorkflowInstance)

        return db.session.query(
            WorkflowInstance.id.label("instance_id"),
            WorkflowTemplate.name.label("template_name"),
            WorkflowStep.step_order,
            WorkflowInstance.form_data,
            # User.display_name.label("initiator_name"),
            WorkflowInstance.created_at
        ).join(
            WorkflowTemplate,
            WorkflowInstance.template_id == WorkflowTemplate.id  # 显式指定模板关联
        ).join(
            WorkflowStep,
            (WorkflowTemplate.id == WorkflowStep.template_id) &  # 双重条件确保准确关联
            (WorkflowInstance.current_step == WorkflowStep.step_order)
            # ).join(
            #     User,
            #     WorkflowInstance.initiator_id == User.id  # 明确用户关联条件
        ).filter(
            WorkflowInstance.status == 'PENDING',
            # func.json_contains(WorkflowStep.approver_ids, [str(user_id)]),  # JSON数组包含检查
            WorkflowStep.approver_ids.contains(str(user_id)),  # JSON数组包含检查
            ~WorkflowInstance.id.in_(subquery)  # 排除已审批记录
        ).order_by(
            WorkflowInstance.created_at.desc()
        ).paginate(
            page=page_number, per_page=page_size, error_out=False
        )

    @classmethod
    def _is_step_completed(cls, instance):
        """判断当前步骤是否完成"""
        current_step = WorkflowStep.query.filter_by(
            template_id=instance.template_id,
            step_order=instance.current_step
        ).first()

        # 获取所有指定审批人
        required_approvers = set(map(int, current_step.approver_ids))

        # 获取实际审批人
        approvals = ApprovalRecord.query.filter_by(
            instance_id=instance.id,
            step_order=instance.current_step
        )
        approved_users = {a.approver_id for a in approvals if a.decision == 'APPROVE'}

        # 根据审批模式判断
        if current_step.approve_mode == 'ANY':
            return len(approved_users & required_approvers) > 0
        else:
            return approved_users.issuperset(required_approvers)

    # 获取审批进度
    @classmethod
    def get_approval_progress(cls, instance_id):
        # 根据实例id获取工作流实例
        instance = WorkflowInstance.query.get_or_404(instance_id)
        # 根据模板id获取步骤，并按步骤顺序排序
        steps = WorkflowStep.query.filter_by(template_id=instance.template_id).order_by('step_order')
        # 返回每个步骤的审批进度
        return [{
            'step_order': s.step_order,
            'status': 'completed' if s.step_order < instance.current_step else 'current' if s.step_order == instance.current_step else 'pending',
            'approvers': [a.approver_id for a in ApprovalRecord.query.filter_by(instance_id=instance_id, step_order=s.step_order).all()]
        } for s in steps]

    # 判断是否为最后一个步骤
    @classmethod
    def _is_final_step(cls, instance):
        # 获取模板id对应的最后一个步骤的步骤顺序
        return instance.current_step == db.session.query(db.func.max(WorkflowStep.step_order)).filter_by(template_id=instance.template_id).scalar()
